package com.pic.mgt.haishin.action;

import java.io.File;

import org.springframework.dao.DataAccessException;

import com.pic.mgt.IgxStatus;
import com.pic.mgt.dao.haishin.HaishinBusinessMgtInfoBean;
import com.pic.mgt.dao.haishin.IHaishinBusinessMgtDao;
import com.pic.mgt.log.IgxLog;
import com.pic.mgt.monitor.backup.UnitBackup;
import com.pic.mgt.unit.Business;
import com.pic.mgt.unit.operation.BusinessUnitOperation;
import com.pic.mgt.unit.operation.UnitOperationException;

public class HaishinBusinessResendActionImpl implements
		HaishinBusinessResendAction {
	
	private IHaishinBusinessMgtDao haishinBusinessMgtDao;
	private UnitBackup businessUnitBackup;
	private BusinessUnitOperation businessUnitOperation;
	private String haishinInboxPathStr;
	private File haishinInboxPath;

	@Override
	public synchronized boolean resendBusinessToTerminal(String targetFilename,
										 				 String asignedTerminal) {
		if (null == targetFilename || targetFilename.isEmpty() || 
			null == asignedTerminal || asignedTerminal.isEmpty()) {
			// ********************** Log **********************
			IgxLog.messageLog.warn(this,
							"Resending business to terminal failed. Did not provide target file name or asigned terminal.");
			// ********************** Log **********************
			
			return false;
		}
		
		
		// ********************** Log **********************
		IgxLog.messageLog.info(this,
						"Starting resend business '{}' to terminal '{}' preprocess.",
						targetFilename, asignedTerminal);
		// ********************** Log **********************
		
		
		// 先從資料庫中找出該業務記錄
		HaishinBusinessMgtInfoBean haishinBusinessMgtInfoBean = 
				this.haishinBusinessMgtDao.findHaishinBusinessMgtInfoByUnitName(targetFilename);
		// 檢查上一次執行狀態是否為完成,完成才可以做重配
		if (null == haishinBusinessMgtInfoBean ||
			!haishinBusinessMgtInfoBean.getStatus().equals(IgxStatus.BUSINESS_COMPLETED)) {
			// ********************** Log **********************
			IgxLog.messageLog.error(this,
							"SUDA-217 Resending haishin business preprocess failed. Because the business '{}' reocrd can't find in database or was not successful execution since last time.",
							targetFilename);
			// ********************** Log **********************
			return false;
		}
		
		// 取得在備份路徑下的業務檔案出來(包含確認檔)
		
		// 取得備份路徑
		File businessBackupPath = this.businessUnitBackup.
											getBackupUnitPath(haishinBusinessMgtInfoBean.getLoadingTime());
		// 取得備份路徑下的目標檔
		File targetFile = new File(businessBackupPath.getAbsolutePath(),
								   haishinBusinessMgtInfoBean.getTargetFile());
		// 取得備份路徑下的確認檔
		File confirmationFile = new File(businessBackupPath.getAbsolutePath(),
										 haishinBusinessMgtInfoBean.getConfirmationFile());
		
		// 建立出一個只包含有確認檔和目標檔的空業務出來 (給 businessUnitOperation 使用)
		Business business = new Business(null);
		business.setConfirmationFile(confirmationFile);
		business.setTargetFile(targetFile);
		
		// 更新資料庫為將重配給端末的狀態
		try {
			// throws DataAccessException
			this.haishinBusinessMgtDao.updateStatusRedoAsginTerminalFileAndRedoAsginTerminalByUnitName(
						IgxStatus.BUSINESS_REDO, asignedTerminal, null, haishinBusinessMgtInfoBean.getUnitName());
		} catch (DataAccessException e) {
			// ********************** Log **********************
			IgxLog.messageDetailsLog.error(this, e.getMessage());
			// ********************** Log **********************
			
			// ********************** Log **********************
			IgxLog.messageLog.error(this,
					"SUDA-218 Resending business '{}' to terminal '{}' preprocess occured a database operation error.",
							targetFilename);
			// ********************** Log **********************
			return false;
		}
		
		// 將業務複製到 haishin inbox 底下
		try {
			this.businessUnitOperation.copyTargetFile(business, this.haishinInboxPath);
			this.businessUnitOperation.copyConfirmationFile(business, this.haishinInboxPath);
		} catch (UnitOperationException e) {
			// ********************** Log **********************
			IgxLog.messageLog.error(this,
					"SUDA-219 Resending business '{}' to terminal '{}' preprocess failed in copying business file to haishin inbox step.",
							targetFilename, asignedTerminal);
			// ********************** Log **********************
			
			// 把資料庫狀態復原回原來的 COMPLETED
			// throws DataAccessException
			try {
				this.haishinBusinessMgtDao.updateStatusRedoAsginTerminalFileAndRedoAsginTerminalByUnitName(
							IgxStatus.BUSINESS_COMPLETED, null, null, haishinBusinessMgtInfoBean.getUnitName());
			} catch (DataAccessException e1) {
				// ********************** Log **********************
				IgxLog.messageDetailsLog.error(this, e.getMessage());
				// ********************** Log **********************
				
				// ********************** Log **********************
				IgxLog.messageLog.error(this,
						"SUDA-218 Resending business '{}' to terminal '{}' preprocess occured a database operation error.",
								targetFilename, asignedTerminal);
				// ********************** Log **********************
			}
			
			return false;
		}
		
		// ********************** Log **********************
		IgxLog.messageLog.info(this,
						"Resending business '{}' to terminal '{}' preprocess completed.",
						targetFilename, asignedTerminal);
		// ********************** Log **********************
		
		return true;
	}
	
	// --- getter and setter ---

	public void setHaishinBusinessMgtDao(
			IHaishinBusinessMgtDao haishinBusinessMgtDao) {
		this.haishinBusinessMgtDao = haishinBusinessMgtDao;
	}

	public void setBusinessUnitBackup(UnitBackup businessUnitBackup) {
		this.businessUnitBackup = businessUnitBackup;
	}

	public void setBusinessUnitOperation(BusinessUnitOperation businessUnitOperation) {
		this.businessUnitOperation = businessUnitOperation;
	}
	
	public void setHaishinInboxPathStr(String haishinInboxPathStr) {
		this.haishinInboxPathStr = haishinInboxPathStr;
		this.haishinInboxPath = new File(haishinInboxPathStr);
	}
}
